package mx.itesm.manejadores;

import org.andengine.engine.Engine;
import org.andengine.engine.handler.timer.ITimerCallback;
import org.andengine.engine.handler.timer.TimerHandler;

import mx.itesm.escenas.EscenaAbout;
import mx.itesm.escenas.EscenaBase;
import mx.itesm.escenas.EscenaCargando;
import mx.itesm.escenas.EscenaElegirNivel;
import mx.itesm.escenas.EscenaElegirPersonaje;
import mx.itesm.escenas.EscenaGanaste;
import mx.itesm.escenas.EscenaInstructions;
import mx.itesm.escenas.EscenaLogoJuego;
import mx.itesm.escenas.EscenaMenu;
import mx.itesm.escenas.EscenaPausa;
import mx.itesm.escenas.EscenaPerdiste;
import mx.itesm.escenas.EscenaScores;
import mx.itesm.escenas.EscenaSettings;
import mx.itesm.escenas.EscenaSplash;
import mx.itesm.escenas.TipoEscena;
import mx.itesm.niveles.Nivel1;
import mx.itesm.niveles.Nivel2;
import mx.itesm.niveles.Nivel3;

/* 
 * **************************************************************
 *                       Variables del manejador de escenas
 * **************************************************************
 */

//NOTA: La escena de elegir personaje aun no es funcional en el juego.

public class ManejadorEscenas {

	// Tipos de Escenas del Juego
	private EscenaBase escenaSplash;		// ----> Implementada!
	private EscenaBase escenaLogoJuego;		// ----> Implementada!
	private EscenaBase escenaMenu;			// ----> Implementada!
	private EscenaBase escenaSettings;		// ----> Implementada!
	private EscenaBase escenaInstruct;		// ----> Implementada!
	private EscenaBase escenaScores;		// ----> Implementada!
	private EscenaBase escenaAbout;			// ----> Implementada!
	private EscenaBase escenaCargando;		// ----> Implementada!
	private EscenaBase escenaElegirPersonaje;	// ----> Implementada!
	private EscenaBase escenaElegirNivel;	// ----> Implementada!
	private EscenaBase escenaGanaste;		// ----> Implementada!
	private EscenaBase escenaPerdiste;		// ----> Implementada!
	private EscenaBase escenaPausa;			// ----> Implementada!

	private EscenaBase escenaNivel1;		// ----> Implementada!
	private EscenaBase escenaNivel2;
	private EscenaBase escenaNivel3;		// ----> Implementada!

	//Instancia del Manejador de Escenas
	private static final ManejadorEscenas INSTANCIA = new ManejadorEscenas();

	// Variables a utilizar
	private TipoEscena tipoEscenaActual = TipoEscena.ESCENA_SPLASH;
	private EscenaBase escenaActual;
	private Engine engine = ManejadorRecursos.getInstance().engine;

	/*
	 * ************************************************************************
	 * Metodos de la clase "ManejadorEscenas"
	 * ************************************************************************
	 */

	// GETTERS: INSTANCIA, TIPO, ESCENA_ACTUAL
	public static ManejadorEscenas getInstance() {
		return INSTANCIA;
	}

	public TipoEscena getTipoEscenaActual() {
		return tipoEscenaActual;
	}

	public EscenaBase getEscenaActual() {
		return escenaActual;
	}

	public void setEscenaBase(EscenaBase esc) {
		engine.setScene(esc);
		escenaActual = esc;
		tipoEscenaActual = esc.getTipoEscena();
	}

	public void setEscena(TipoEscena tipo) {
		switch(tipo) {

		case ESCENA_SPLASH:
			setEscenaBase(escenaSplash);
			break;
			
		case ESCENA_LOGO:
			setEscenaBase(escenaLogoJuego);
			break;

		case ESCENA_MENU:
			setEscenaBase(escenaMenu);
			break;

		case ESCENA_SETTINGS:
			setEscenaBase(escenaSettings);
			break;

		case ESCENA_INSTRUCT:
			setEscenaBase(escenaInstruct);
			break;

		case ESCENA_SCORES:
			setEscenaBase(escenaScores);
			break;

		case ESCENA_ABOUT:
			setEscenaBase(escenaAbout);
			break;

		case ESCENA_CARGAR:
			setEscenaBase(escenaCargando);
			break;

		case ESCENA_ELEGIR_PERSONAJE:
			setEscenaBase(escenaElegirPersonaje);
			break;

		case ESCENA_ELEGIR_NIVEL:
			setEscenaBase(escenaElegirNivel);
			break;

		case ESCENA_GANASTE:
			setEscenaBase(escenaGanaste);
			break;

		case ESCENA_PERDISTE:
			setEscenaBase(escenaPerdiste);
			break;

		case ESCENA_PAUSA:
			setEscenaBase(escenaPausa);
			break;
			
		case ESCENA_LV1:
			setEscenaBase(escenaNivel1);
			break;
			
		case ESCENA_LV2:
			setEscenaBase(escenaNivel2);
			break;
			
		case ESCENA_LV3:
			setEscenaBase(escenaNivel3);
			break;

		default:
			break;
		}
	}

	/* Splash Scene */

	//Crear Splash Scene
	public void cargarEscenaSplash() {
		ManejadorRecursos.getInstance().cargarSplashScreen();
		escenaSplash = new EscenaSplash();
	}

	//Descargar Splash Scene
	public void descargarEscenaSplash() {
		ManejadorRecursos.getInstance().descargarSplashScreen();
		escenaSplash.removerEscena();
		escenaSplash = null;
	}
	
	/* Logo Scene */
	
	public void cargarEscenaLogoJuego() {
		ManejadorRecursos.getInstance().cargarRecursosLogo();
		escenaLogoJuego = new EscenaLogoJuego();
	}
	
	public void descargarEscenaLogoJuego() {
		ManejadorRecursos.getInstance().descargarRecursosLogo();
		escenaLogoJuego.removerEscena();
		escenaLogoJuego = null;
	}

	/* Main Menu Scene */

	//Cargar Main Menu Scene
	public void cargarEscenaMenu() {
		ManejadorRecursos.getInstance().cargarRecursosMenu();
		escenaMenu = new EscenaMenu();
	}

	//Descargar Main Menu Scene
	public void descargarEscenaMenu() {
		ManejadorRecursos.getInstance().descargarRecursosMenu();
		escenaMenu.removerEscena();
		escenaMenu = null;
	}

	/* Loading Menu Scene */

	//Cargar la escena Loading
	public void cargarEscenaLoading() {
		ManejadorRecursos.getInstance().cargarRecursosLoading();
		escenaCargando = new EscenaCargando();
	}

	//Descargar la escena Loading
	public void descargarEscenaLoading() {
		ManejadorRecursos.getInstance().descargarRecursosLoading();
		escenaCargando.removerEscena();
		escenaCargando = null;
	}

	/* About Menu Scene */

	//Cargar la About Scene
	public void cargarEscenaAbout() {
		cargarEscenaLoading();
		setEscena(TipoEscena.ESCENA_CARGAR);
		descargarEscenaMenu();

		engine.registerUpdateHandler(new TimerHandler(0.2f, new ITimerCallback() {

			@Override
			public void onTimePassed(final TimerHandler pTimerHandler) {
				engine.unregisterUpdateHandler(pTimerHandler);
				ManejadorRecursos.getInstance().cargarRecursosAbout();
				escenaAbout = new EscenaAbout();
				setEscena(TipoEscena.ESCENA_ABOUT);
			}
		}));
	}

	//Descargar la About Scene
	public void descargarEscenaAbout() {
		ManejadorRecursos.getInstance().descargarRecursosAbout();
		escenaAbout.removerEscena();
		escenaAbout = null;
	}

	/* Instructions Menu Scene */

	//Cargar la Instructions Scene
	public void cargarEscenaInstructions() {
		cargarEscenaLoading();
		setEscena(TipoEscena.ESCENA_CARGAR);
		descargarEscenaMenu();

		engine.registerUpdateHandler(new TimerHandler(0.2f, new ITimerCallback() {

			@Override
			public void onTimePassed(final TimerHandler pTimerHandler) {

				engine.unregisterUpdateHandler(pTimerHandler);
				ManejadorRecursos.getInstance().cargarRecursosInstructions();
				escenaInstruct = new EscenaInstructions();
				setEscena(TipoEscena.ESCENA_INSTRUCT);
			}
		}));
	}

	//Descargar la Instructions Scene
	public void descargarEscenaInstructions() {
		ManejadorRecursos.getInstance().descargarRecursosInstructions();
		escenaInstruct.removerEscena();
		escenaInstruct = null;
	}

	/* Scores Menu Scene */

	//Cargar la Scores Scene
	public void cargarEscenaScores() {
		cargarEscenaLoading();
		setEscena(TipoEscena.ESCENA_CARGAR);
		descargarEscenaMenu();

		engine.registerUpdateHandler(new TimerHandler(0.2f, new ITimerCallback() {

			@Override
			public void onTimePassed(final TimerHandler pTimerHandler) {

				engine.unregisterUpdateHandler(pTimerHandler);
				ManejadorRecursos.getInstance().cargarRecursosScores();
				escenaScores = new EscenaScores();
				setEscena(TipoEscena.ESCENA_SCORES);
			}
		}));
	}

	//Descargar la Scores Scene
	public void descargarEscenaScores() {
		ManejadorRecursos.getInstance().descargarRecursosScores();
		escenaScores.removerEscena();
		escenaScores = null;
	}

	/* Settings Menu Scene */

	//Cargar la Settings Scene
	public void cargarEscenaSettings() {
		cargarEscenaLoading();
		setEscena(TipoEscena.ESCENA_CARGAR);
		descargarEscenaMenu();

		engine.registerUpdateHandler(new TimerHandler(0.2f, new ITimerCallback() {

			@Override
			public void onTimePassed(final TimerHandler pTimerHandler) {

				engine.unregisterUpdateHandler(pTimerHandler);
				ManejadorRecursos.getInstance().cargarRecursosSettings();
				escenaSettings = new EscenaSettings();
				setEscena(TipoEscena.ESCENA_SETTINGS);
			}
		}));
	}

	//Descargar la Settings Scene
	public void descargarEscenaSettings() {
		ManejadorRecursos.getInstance().descargarRecursosSettings();
		escenaSettings.removerEscena();
		escenaSettings = null;
	}

	/* Elegir Personaje */

	//Cargar escena Elegir Personaje
	public void cargarEscenaElegirPersonaje() {	
		ManejadorRecursos.getInstance().cargarRecursosElegirPersonaje();
		escenaElegirPersonaje = new EscenaElegirPersonaje();
		setEscena(TipoEscena.ESCENA_ELEGIR_PERSONAJE);
	}

	//Descargar escena Elegir Personaje
	public void descargarEscenaElegirPersonaje() {
		ManejadorRecursos.getInstance().descargarRecursosElegirPersonaje();
		escenaElegirPersonaje.removerEscena();
		escenaElegirPersonaje = null;
	}

	/* Elegir Nivel */

	// Cargar escena para elegir nivel
	public void cargarEscenaElegirNivel() {
		ManejadorRecursos.getInstance().cargarRecursosElegirNivel();
		escenaElegirNivel = new EscenaElegirNivel();
	}

	// Descargar escena de elegir nivel
	public void descargarEscenaElegirNivel() {
		ManejadorRecursos.getInstance().descargarRecursosElegirNivel();
		escenaElegirNivel.removerEscena();
		escenaElegirNivel = null;
	}

	/* Escena Ganaste */

	// Cargar escena nivel superado
	public void cargarEscenaGanaste() {
		ManejadorRecursos.getInstance().cargarRecursosGanaste();
		escenaGanaste = new EscenaGanaste();
	}

	// Descargar escena nivel superado
	public void descargarEscenaGanaste() {
		ManejadorRecursos.getInstance().descargarRecursosGanaste();
		escenaGanaste.removerEscena();
		escenaGanaste = null;
	}

	/* Escena Perdiste */

	// Cargar escena perdiste
	public void cargarEscenaPerdiste() {
		ManejadorRecursos.getInstance().cargarRecursosPerdiste();
		escenaPerdiste = new EscenaPerdiste();
	}

	// Descargar escena perdiste
	public void descargarEscenaPerdiste() {
		ManejadorRecursos.getInstance().descargarRecursosPerdiste();
		escenaPerdiste.removerEscena();
		escenaPerdiste = null;
	}

	/* Escena Pausa */
	
	// Cargar escena pausa del juego
	public void cargarEscenaPausa() {
		ManejadorRecursos.getInstance().cargarRecursosPausa();
		escenaPausa = new EscenaPausa();
	}
	
	// Descargar escena pausa del juego
	public void descargarEscenaPausa() {
		ManejadorRecursos.getInstance().descargarRecursosPausa();
		escenaPausa.removerEscena();
		escenaPausa = null;
	}
	
	/* Escena Nivel 1 */
	
	// Cargar escena nivel 1
	public void cargarEscenaNivel1() {
		ManejadorRecursos.getInstance().cargarRecursosNivel1();
	//	ManejadorRecursos.getInstance().cargarRecursosBotones();
		escenaNivel1 = new Nivel1();
	}
	
	// Descargar escena nivel 1
	public void descargarEscenaNivel1() {
		ManejadorRecursos.getInstance().descargarRecursosNivel1();
		escenaNivel1.removerEscena();
		escenaNivel1 = null;
	}
	
	/* Escena Nivel 2 */
	
	// Cargar escena nivel 1
	public void cargarEscenaNivel2() {
		ManejadorRecursos.getInstance().cargarRecursosNivel2();
		escenaNivel2 = new Nivel2();
	}

	// Descargar escena nivel 1
	public void descargarEscenaNivel2() {
		ManejadorRecursos.getInstance().descargarRecursosNivel2();
		escenaNivel2.removerEscena();
		escenaNivel2 = null;
	}
	
	/* Escena Nivel 3 */
	
	// Cargar escena prueba
	public void cargarEscenaNivel3() {
		ManejadorRecursos.getInstance().cargarRecursosNivel3();
		escenaNivel3 = new Nivel3();
	}
	
	// Descargar escena prueba
	public void descargarEscenaNivel3() {
		ManejadorRecursos.getInstance().descargarRecursosNivel3();
		escenaNivel3.removerEscena();
		escenaNivel3 = null;
	}
}
